<!--
 * @Author: Zesion Lee
 * @Date: 2025-07-14 10:39:29
 * @Description: 文件浏览器弹窗
-->
<template>
  <Teleport to="body">
    <div id="FileExBox" v-if="show">
      <div class="fileExplore">
        <div class="title">
          <span>选择文件</span>
          <CloseOutlined @click="show = false" />
        </div>

        <div class="fzBody">
          <div class="position">
            <template v-for="(sub, index) in curerntList" :key="index">
              <span
                @click="jump2(sub, index)"
                :class="{ current: index == curerntList.length - 1 }"
                v-if="index == 0 || (index > 0 && sub)"
                >{{ sub || 'root' }}</span
              >
            </template>
          </div>
          <div class="fix">
            <li v-for="disk in datas.disks" @click="setCurrent('\\' + disk.name, true)">
              <IconDisk style="margin-right: 3px" /> {{ disk.name }}
            </li>
          </div>
          <div class="list">
            <li
              v-for="sub in datas.subs"
              @dblclick="dbClickItem(sub)"
              @click="datas.curentSelect = sub"
              :class="{ select: datas.curentSelect == sub }"
            >
              <span>
                <FolderOpenOutlined v-if="sub.type == 'dir'" />
                <IconDisk v-else-if="sub.type == 'disk'" />
                <FileOutlined v-else />
              </span>

              <span> {{ sub.name }}</span>
            </li>
          </div>
          <div class="placement"></div>
          <div class="footer">
            <a-button type="default" @click="show = false">取消</a-button>
            <a-button type="primary" @click="setPath">确定</a-button>
          </div>
        </div>
      </div>
    </div>
  </Teleport>
</template>

<script setup lang="ts">
import { computed, onMounted, reactive, Teleport, watch } from 'vue'
import { CloseOutlined, FileOutlined, FolderOpenOutlined } from '@ant-design/icons-vue'
import IconDisk from '../icons/IconDisk.vue'
import axios from 'axios'
import type { Res } from '@/http'
import { message } from 'ant-design-vue'
const props = defineProps<{
  type: string
}>()

const show = defineModel<boolean>('show')

const baseUrl = import.meta.env.VITE_HTTP_BASE_URL

const dbClickItem = async (sub: subDir) => {
  if (sub.type == 'dir' || sub.type == 'disk') await setCurrent('\\' + sub.name)
  else setPath()
}

interface subDir {
  ext: string
  name: string
  type: string
}

const datas = reactive<{
  disks: subDir[]
  subs: subDir[]
  current: string
  curentSelect?: subDir
}>({
  disks: [],
  subs: [],
  current: '',
  curentSelect: undefined,
})

const curerntList = computed(() => datas.current.split('\\'))

const jump2 = (sub: string, index: number) => {
  if (index == curerntList.value.length - 1) return
  const list = curerntList.value.slice(0, index + 1)

  if (index == 1) setCurrent('\\' + sub + '\\', true)
  else setCurrent(list.join('\\'), true)
}

const setCurrent = async (sub: string, ready: boolean = false) => {
  datas.curentSelect = undefined
  datas.current = ready ? sub : datas.current + sub

  const res = await axios.get<Res>(encodeURI(`${baseUrl}/file/get-sub?sub=${datas.current}`))
  const { code, data, msg } = res.data

  if (code == 200) {
    datas.subs = data
  }

  if (sub.length == 0) {
    datas.disks = data
  }
}

onMounted(() => {
  setCurrent('')
})

const emit = defineEmits(['close'])

const setPath = () => {
  let finnalPath = datas.current

  if (props.type == 'dir') {
    if (datas.curentSelect) {
      if (datas.curentSelect.type == 'dir' || datas.curentSelect.type == 'disk') {
        finnalPath += '\\' + datas.curentSelect.name
      } else {
        message.warn('请选择文件夹')
        return
      }
    }
  } else {
    if (!datas.curentSelect) {
      message.warn('未选择文件！')
      return
    }

    if (datas.curentSelect.ext != props.type) {
      message.warn(`请选择${props.type}文件！`)
      return
    }
    finnalPath += '\\' + datas.curentSelect.name
  }
  emit('close', finnalPath.slice(1))

  datas.curentSelect = undefined
  show.value = false
}
</script>

<style scoped lang="less">
#FileExBox {
  position: absolute;
  top: 0;
  left: 0;
  height: 100vh;
  width: 100vw;
  background-color: #00000065;
  display: flex;
  align-items: center;
  justify-content: center;

  .fileExplore {
    width: 80%;
    max-width: 800px;
    height: 64%;
    background-color: aliceblue;
    border: 1px solid #f8f8f8;
    border-radius: 8px;
    box-shadow: 0 10px 20px 0px #929292;

    .title {
      padding: 6px 8px;
      border-bottom: 1px solid #c5c5c5;
      display: flex;
      justify-content: space-between;
      align-items: center;
      span:nth-child(2) {
        cursor: pointer;
      }
    }
    .fzBody {
      display: grid;
      height: calc(100% - 38px);
      grid-template-columns: 180px 1fr;
      grid-template-rows: 34px 1fr 1fr 38px;
      grid-gap: 5px;
      padding: 4px 5px;
      background-color: #e9e9e9;
      overflow: hidden;

      div {
        // border: 1px solid #f00;
        background-color: #fff;
        border-radius: 5px;
      }
      .footer,
      .position {
        grid-column-start: 1;
        grid-column-end: 3;
        align-items: center;
        display: flex;
        padding: 0 10px;
      }
      .position {
        span {
          margin-right: 3px;
          display: inline-block;
          min-width: 30px;
          border: 1px solid #929292;
          text-align: center;
          padding: 2px 5px;
          border-radius: 5px;
        }
        span:hover {
          cursor: pointer;
          color: #1890ff;
          border-color: #1890ff;
        }
        span.current {
          background-color: #1890ff22;
          color: #1890ff;
          font-weight: 600;
          cursor: default;
        }
      }
      .footer {
        justify-content: flex-end;
        button {
          margin-left: 30px;
        }
      }
      .fix {
        padding: 5px 6px;
        overflow: auto;
        li {
          display: flex;
          align-items: center;
          font-size: 16px;
          user-select: none;
          padding: 1px 3px;
        }

        li:hover {
          background-color: #1890ff65;
        }
      }
      .list {
        grid-row-start: 2;
        grid-column-start: 2;
        grid-row-end: 4;
        padding: 5px 6px;
        overflow: auto;

        li {
          user-select: none;
          display: flex;
          align-items: center;
          padding: 3px 0;

          //   background-color: #1890ff;
        }
        li.select,
        li:hover {
          background-color: #1890ff65;
        }
        li > span:nth-child(1) {
          padding: 0 5px;
          font-size: 18px;
          display: flex;
        }
      }
    }
  }
}
</style>
